package com.vegetable.modules.service.wx.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.vegetable.common.async.AsyncWechatService;
import com.vegetable.common.utils.Constant;
import com.vegetable.common.utils.HttpUtil;
import com.vegetable.modules.entity.sys.SysUserEntity;
import com.vegetable.modules.entity.wx.WXApproval;
import com.vegetable.modules.entity.wx.po.QueryWXApprovalPO;
import com.vegetable.modules.entity.wx.po.UpdatePaymentStatusPO;
import com.vegetable.modules.mapper.wx.WXApprovalDao;
import com.vegetable.modules.service.sys.SysUserService;
import com.vegetable.modules.service.wx.WXApprovalService;
import lombok.extern.slf4j.Slf4j;
import me.chanjar.weixin.common.error.WxErrorException;
import me.chanjar.weixin.cp.api.WxCpService;
import me.chanjar.weixin.cp.bean.WxCpUser;
import me.chanjar.weixin.cp.bean.message.WxCpMessage;
import me.chanjar.weixin.cp.bean.message.WxCpMessageSendResult;
import me.chanjar.weixin.cp.bean.oa.WxCpApprovalApplyData;
import me.chanjar.weixin.cp.bean.oa.WxCpApprovalDetailResult;
import me.chanjar.weixin.cp.bean.oa.WxCpApprovalInfo;
import me.chanjar.weixin.cp.bean.oa.WxCpSpStatus;
import me.chanjar.weixin.cp.bean.oa.WxCpOaApplyEventRequest;
import me.chanjar.weixin.cp.bean.oa.applydata.ApplyDataContent;
import me.chanjar.weixin.cp.bean.oa.applydata.ContentValue;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.*;

@Slf4j
@Service()
public class WXApprovalServiceImpl extends ServiceImpl<WXApprovalDao, WXApproval> implements WXApprovalService {
    @Value("${wechat.cp.corpId}")
    private String corpId;
    @Value("${wechat.cp.appConfig.secret}")
    private String corpSecret;
    @Autowired
    private SysUserService sysUserService;
    @Autowired
    private WxCpService wxCpService;
    @Autowired
    private AsyncWechatService asyncWechatService;

    @Scheduled(cron = "0 0 22 * * ?")
    @Override
    public void importFromWX() throws Exception {
        log.info("开始拉取审批信息。");
        List<String> noList = getReleaseApprovalList();
        if(CollectionUtil.isNotEmpty(noList)){
            for(String no : noList){
                WxCpApprovalDetailResult detail = getReleaseApprovalDetail(no);
                if(0 == detail.getErrCode()){
                    log.info("根据docNo:{}拉取审批信息成功：{}", no, detail);
                    WXApproval approval = getWxApproval(detail);
                    if (approval == null) continue;
                    saveOrUpdate(approval);
                }else {
                    log.info("获取审批信息失败：{}", detail);
                }
            }
        }else{
            log.info("没有新的审批");
        }
    }

    /**
     * 从微信返回信息拼凑新系统参数
     * @param detail
     * @return
     * @throws WxErrorException
     */
    @Override
    public WXApproval getWxApproval(WxCpApprovalDetailResult detail) throws WxErrorException {
        WxCpApprovalDetailResult.WxCpApprovalDetail approvalInfo = detail.getInfo();
        String spName = approvalInfo.getSpName();
        // 处理报销和付款审批两种类型
        if(!"报销".equals(spName) && !"付款审批".equals(spName)){
            log.info("其他报销类型:{} 暂时不处理", spName);
            return null;
        }
        String spNo = approvalInfo.getSpNo();
        WXApproval approval = selectBySPNO(spNo);
        
        // 如果数据库状态是 ALREADY_PAY 或 PASSED，跳过更新
        if(ObjectUtil.isNotNull(approval)){
            String dbStatus = approval.getSpStatus();
            if("ALREADY_PAY".equals(dbStatus) || "PASSED".equals(dbStatus)){
                log.info("审批编号: {} 数据库状态为 {}，跳过更新", spNo, dbStatus);
                return null;
            }
        }
        
        if(ObjectUtil.isNull(approval)){
            approval = new WXApproval();
        }
        Long applyTime = approvalInfo.getApplyTime();
        WxCpSpStatus spStatus = approvalInfo.getSpStatus();
        approval.setSpStatus(spStatus.name());
        String userId = approvalInfo.getApplier().getUserId();
        String reimbursementType = "";
        WxCpApprovalApplyData applyData = approvalInfo.getApplyData();
        List<ApplyDataContent> contents = applyData.getContents();
        for(ApplyDataContent adc : contents){
            if(adc.getId().equals("item-1503317593875")){
                List<ContentValue.Selector.Option> options = adc.getValue().getSelector().getOptions();
                for(ContentValue.Selector.Option title : options){
                    reimbursementType = title.getValues().get(0).getText();
                    break;
                }

            }
            if(adc.getId().equals("item-1503317853434")){
                List<ContentValue.Child> options = adc.getValue().getChildren();
                List<ApplyDataContent> opts = options.get(0).getList();
                String aMoney = opts.stream().filter(el -> el.getControl().equals("Money")).findAny().get().getValue().getNewMoney();
                String aDes = opts.stream().filter(el -> el.getControl().equals("Textarea")).findAny().get().getValue().getText();
                approval.setMoney(new BigDecimal(aMoney));
                approval.setApprovalContent(aDes);
//                break;
            }
            if(adc.getId().equals("Selector-1750403962373")){
                List<ContentValue.Selector.Option> options = adc.getValue().getSelector().getOptions();
                String regionName = options.get(0).getValues().get(0).getText();
                Integer regionId = Constant.LedgerRegion.getCodeByName(regionName);
                approval.setRegionId(regionId);
            }
        }
        WxCpUser cpUser = wxCpService.getUserService().getById(userId);
        approval.setUserId(cpUser.getUserId());
        approval.setUserName(cpUser.getName());
        approval.setSpComment(JSONObject.toJSONString(detail));
        approval.setSpNo(spNo);
        approval.setSpName(spName);
        approval.setApplyTime(new Date(applyTime * 1000));
        approval.setReimbursementType(reimbursementType);

        WXApproval existApp = selectBySPNo(approval.getSpNo());
        if(ObjectUtil.isNotNull(existApp)){
            approval.setId(existApp.getId());
        }
        return approval;
    }

    @Override
    public void convertToUserId() throws Exception {
        List<SysUserEntity> userList = sysUserService.getBaseMapper().selectList(new QueryWrapper<>());
        // 使用SDK的现成接口获取企业微信用户ID
        for(SysUserEntity entity : userList){
            try {
                String userMobile = entity.getMobile();
                if (StrUtil.isBlank(userMobile)) {
                    log.warn("用户 {} 手机号为空，跳过转换", entity.getUserId());
                    continue;
                }
                
                // 使用SDK的getUserId方法，通过手机号获取企业微信用户ID
                String wxUserId = wxCpService.getUserService().getUserId(userMobile);
                if (StrUtil.isNotBlank(wxUserId)) {
                    SysUserEntity updater = new SysUserEntity();
                    updater.setUserId(entity.getUserId());
                    updater.setWxUserId(wxUserId);
                    sysUserService.updateById(updater);
                    log.info("成功转换用户ID，手机号: {}, 企业微信用户ID: {}", userMobile, wxUserId);
                } else {
                    log.warn("未能获取企业微信用户ID，手机号: {}", userMobile);
                }
            } catch (WxErrorException e) {
                log.error("转换用户ID失败，用户: {}, 错误: {}", entity.getUserId(), e.getMessage());
            }
        }
    }

    /**
     * 获取审批模板详情，用于调试和验证控件ID
     */
    public void getApprovalTemplateDetail() throws WxErrorException {
        String templateId = "BsAa8hbdNHRudQ9TmRntADjRFxQk5Ujcc9bMoSJ9w"; // 使用新的模板ID
        try {
            // 获取模板详情
            me.chanjar.weixin.cp.bean.oa.WxCpOaApprovalTemplateResult templateDetail = 
                wxCpService.getOaService().getTemplateDetail(templateId);
            
            log.info("新的付款审批模板详情: {}", JSONObject.toJSONString(templateDetail));
            
            // 打印控件信息
            if (templateDetail.getTemplateContent() != null && 
                templateDetail.getTemplateContent().getControls() != null) {
                for (me.chanjar.weixin.cp.bean.oa.WxCpOaApprovalTemplateResult.TemplateControls control : 
                     templateDetail.getTemplateContent().getControls()) {
                    if (control.getProperty() != null) {
                        log.info("控件ID: {}, 控件类型: {}, 是否必填: {}", 
                            control.getProperty().getId(),
                            control.getProperty().getControl(),
                            control.getProperty().getRequire());
                    }
                }
            }
        } catch (WxErrorException e) {
            log.error("获取新的付款审批模板详情失败", e);
            throw e;
        }
    }

    /**
     * 测试提交审批，用于验证控件ID是否正确
     */
    public void testSubmitApproval() throws Exception {
        try {
            log.info("开始测试提交企业微信审批");
            
            // 使用企业微信官方SDK的WxCpOaApplyEventRequest替代自定义的ApprovalRequest
            WxCpOaApplyEventRequest ar = new WxCpOaApplyEventRequest();
            ar.setCreatorUserId("Cherry");
            ar.setTemplateId("BsAa8hbdNHRudQ9TmRntADjRFxQk5Ujcc9bMoSJ9w"); // 使用新的模板ID
            ar.setUseTemplateApprover(0); // 不使用模板审批人
            
            // 构建申请数据
            WxCpOaApplyEventRequest.ApplyData ad = new WxCpOaApplyEventRequest.ApplyData();
            List<ApplyDataContent> contentItems = new ArrayList<>();
            
            // 添加付款事由 (必需控件)
            ApplyDataContent reasonContent = new ApplyDataContent();
            reasonContent.setControl("Textarea");
            ContentValue reasonValue = new ContentValue();
            reasonValue.setText("测试付款申请");
            reasonContent.setValue(reasonValue);
            reasonContent.setId("item-1494251039326"); // 付款事由
            contentItems.add(reasonContent);

            // 添加付款金额 (必需控件)
            ApplyDataContent amountContent = new ApplyDataContent();
            amountContent.setControl("Money");
            ContentValue amountValue = new ContentValue();
            amountValue.setNewMoney("1000.00");
            amountContent.setValue(amountValue);
            amountContent.setId("item-1494251052639"); // 付款金额
            contentItems.add(amountContent);
            
            log.info("设置付款金额控件，控件ID: item-1494251052639, 金额值: 1000.00");

            // 添加付款方式 (必需控件) - 默认选择银行卡
            ApplyDataContent methodContent = new ApplyDataContent();
            methodContent.setControl("Selector");
            ContentValue methodValue = new ContentValue();
            methodValue.setSelector(new ContentValue.Selector());
            methodValue.getSelector().setType("single");
            // 修复类型不兼容问题，使用选项键而不是字符串
            List<ContentValue.Selector.Option> options = new ArrayList<>();
            ContentValue.Selector.Option option = new ContentValue.Selector.Option();
            option.setKey("option-3742851564"); // 银行卡选项键
            options.add(option);
            methodValue.getSelector().setOptions(options);
            methodContent.setValue(methodValue);
            methodContent.setId("item-1494251058811"); // 付款方式
            contentItems.add(methodContent);

            // 添加付款日期 (必需控件) - 使用当前日期
            ApplyDataContent dateContent = new ApplyDataContent();
            dateContent.setControl("Date");
            ContentValue dateValue = new ContentValue();
            dateValue.setDate(new ContentValue.Date());
            // 修复方法名，使用正确的方法设置日期
            dateValue.getDate().setTimestamp(String.valueOf(System.currentTimeMillis() / 1000));
            dateContent.setValue(dateValue);
            dateContent.setId("item-1494251158679"); // 付款日期
            contentItems.add(dateContent);

            // 添加收款人全称 (必需控件)
            ApplyDataContent payeeContent = new ApplyDataContent();
            payeeContent.setControl("Text");
            ContentValue payeeValue = new ContentValue();
            payeeValue.setText("测试收款人");
            payeeContent.setValue(payeeValue);
            payeeContent.setId("item-1494251166594"); // 收款人全称
            contentItems.add(payeeContent);

            // 添加银行账号 (必需控件)
            ApplyDataContent accountContent = new ApplyDataContent();
            accountContent.setControl("Text");
            ContentValue accountValue = new ContentValue();
            accountValue.setText("1234567890123456");
            accountContent.setValue(accountValue);
            accountContent.setId("item-1494251179316"); // 银行账号
            contentItems.add(accountContent);

            // 添加开户行 (必需控件)
            ApplyDataContent bankContent = new ApplyDataContent();
            bankContent.setControl("Text");
            ContentValue bankValue = new ContentValue();
            bankValue.setText("中国银行");
            bankContent.setValue(bankValue);
            bankContent.setId("item-1494251194643"); // 开户行
            contentItems.add(bankContent);

            ad.setContents(contentItems);
            ar.setApplyData(ad);
            
            log.info("测试请求参数：{}", JSONObject.toJSONString(ar));
            
            // 调用企业微信API提交审批
            String spNo = wxCpService.getOaService().apply(ar);
            log.info("测试接口返回审批编号：{}", spNo);
        } catch (WxErrorException e) {
            log.error("测试提交审批失败", e);
            throw e;
        }
    }

    @Override
    public void applyApproval() throws Exception {
        // 使用企业微信官方SDK的WxCpOaApplyEventRequest替代自定义的ApprovalRequest
        WxCpOaApplyEventRequest ar = new WxCpOaApplyEventRequest();
        ar.setCreatorUserId("Cherry");
        ar.setTemplateId("BsAa8hbdNHRudQ9TmRntADjRFxQk5Ujcc9bMoSJ9w"); // 更新为新的模板ID
        ar.setUseTemplateApprover(1);
        
        // 构建申请数据
        WxCpOaApplyEventRequest.ApplyData ad = new WxCpOaApplyEventRequest.ApplyData();
        List<ApplyDataContent> contentItems = new ArrayList<>();
        
        // 添加付款事由 (必需控件)
        ApplyDataContent reasonContent = new ApplyDataContent();
        reasonContent.setControl("Textarea");
        ContentValue reasonValue = new ContentValue();
        reasonValue.setText("闫庆龙 12.09 黄瓜结款申请");
        reasonContent.setValue(reasonValue);
        reasonContent.setId("item-1494251039326"); // 付款事由
        contentItems.add(reasonContent);

        // 添加付款金额 (必需控件)
        ApplyDataContent amountContent = new ApplyDataContent();
        amountContent.setControl("Money");
        ContentValue amountValue = new ContentValue();
        amountValue.setNewMoney("21122.00");
        amountContent.setValue(amountValue);
        amountContent.setId("item-1494251052639"); // 付款金额
        contentItems.add(amountContent);

        // 添加付款方式 (必需控件) - 默认选择银行卡
        ApplyDataContent methodContent = new ApplyDataContent();
        methodContent.setControl("Selector");
        ContentValue methodValue = new ContentValue();
        methodValue.setSelector(new ContentValue.Selector());
        methodValue.getSelector().setType("single");
        // 修复类型不兼容问题，使用选项键而不是字符串
        List<ContentValue.Selector.Option> options = new ArrayList<>();
        ContentValue.Selector.Option option = new ContentValue.Selector.Option();
        option.setKey("option-3742851564"); // 银行卡选项键
        options.add(option);
        methodValue.getSelector().setOptions(options);
        methodContent.setValue(methodValue);
        methodContent.setId("item-1494251058811"); // 付款方式
        contentItems.add(methodContent);

        // 添加付款日期 (必需控件) - 使用当前日期
        ApplyDataContent dateContent = new ApplyDataContent();
        dateContent.setControl("Date");
        ContentValue dateValue = new ContentValue();
        dateValue.setDate(new ContentValue.Date());
        // 修复方法名，使用正确的方法设置日期
        dateValue.getDate().setTimestamp(String.valueOf(System.currentTimeMillis() / 1000));
        dateContent.setValue(dateValue);
        dateContent.setId("item-1494251158679"); // 付款日期
        contentItems.add(dateContent);

        // 添加收款人全称 (必需控件)
        ApplyDataContent payeeContent = new ApplyDataContent();
        payeeContent.setControl("Text");
        ContentValue payeeValue = new ContentValue();
        payeeValue.setText("闫庆龙");
        payeeContent.setValue(payeeValue);
        payeeContent.setId("item-1494251166594"); // 收款人全称
        contentItems.add(payeeContent);

        // 添加银行账号 (必需控件)
        ApplyDataContent accountContent = new ApplyDataContent();
        accountContent.setControl("Text");
        ContentValue accountValue = new ContentValue();
        accountValue.setText("1234567890123456");
        accountContent.setValue(accountValue);
        accountContent.setId("item-1494251179316"); // 银行账号
        contentItems.add(accountContent);

        // 添加开户行 (必需控件)
        ApplyDataContent bankContent = new ApplyDataContent();
        bankContent.setControl("Text");
        ContentValue bankValue = new ContentValue();
        bankValue.setText("中国银行");
        bankContent.setValue(bankValue);
        bankContent.setId("item-1494251194643"); // 开户行
        contentItems.add(bankContent);

        ad.setContents(contentItems);
        ar.setApplyData(ad);
        
        log.info("请求参数：{}", JSONObject.toJSONString(ar));
        
        // 调用企业微信API提交审批
        String spNo = wxCpService.getOaService().apply(ar);
        log.info("接口返回审批编号：{}", spNo);
    }

    @Override
    public void listId() throws Exception {
        try {
            // 使用SDK获取部门用户详情列表
            // 获取根部门（部门ID为1）的所有用户
            List<WxCpUser> userList = wxCpService.getUserService().listByDepartment(1L, true, 0);
            log.info("获取到用户数量: {}", userList.size());
            
            // 输出用户ID列表
            List<String> userIds = new ArrayList<>();
            for (WxCpUser user : userList) {
                userIds.add(user.getUserId());
            }
            log.info("用户ID列表: {}", JSONObject.toJSONString(userIds));
        } catch (WxErrorException e) {
            log.error("获取用户ID列表失败", e);
            throw new Exception("获取用户ID列表失败: " + e.getMessage());
        }
    }

    @Override
    public void getUserInfo() throws Exception {
        List<WXApproval> approvals = this.baseMapper.selectList(new QueryWrapper<>());
        // 使用SDK获取用户信息
        for(WXApproval entity : approvals){
            try {
                String userId = entity.getUserId();
                if (StrUtil.isBlank(userId)) {
                    log.warn("审批记录 {} 的用户ID为空，跳过", entity.getId());
                    continue;
                }
                
                // 使用SDK的getById方法获取用户信息
                WxCpUser cpUser = wxCpService.getUserService().getById(userId);
                if (cpUser != null && StrUtil.isNotBlank(cpUser.getName())) {
                    WXApproval updater = new WXApproval();
                    updater.setId(entity.getId());
                    updater.setUserName(cpUser.getName());
                    this.updateById(updater);
                    log.info("成功更新用户信息，用户ID: {}, 用户名: {}", userId, cpUser.getName());
                } else {
                    log.warn("未能获取用户信息，用户ID: {}", userId);
                }
            } catch (WxErrorException e) {
                log.error("获取用户信息失败，审批记录ID: {}, 错误: {}", entity.getId(), e.getMessage());
            }
        }
    }

    @Override
    public List<WXApproval> selectBySPNOList(List<String> spNOList) {
        QueryWrapper<WXApproval> wrapper = new QueryWrapper<>();
        wrapper.in("sp_no", spNOList);
        return baseMapper.selectList(wrapper);
    }

    @Override
    public WXApproval selectBySPNO(String spNO) {
        QueryWrapper<WXApproval> wrapper = new QueryWrapper<>();
        wrapper.eq("sp_no", spNO);
        return baseMapper.selectOne(wrapper);
    }

    @Override
    public Map<String, Object> selectList(QueryWXApprovalPO po) {
        Map<String, Object> result = new HashMap<>();
        List<Map<String, Object>> userList = new ArrayList<>();
        QueryWrapper<WXApproval> userQuery = new QueryWrapper<>();
        userQuery.groupBy("user_id");
        List<WXApproval> users = baseMapper.selectList(userQuery);
        for (WXApproval approval : users) {
            Map<String, Object> user = new HashMap<>();
            user.put("userId", approval.getUserId());
            user.put("userName", approval.getUserName());
            userList.add(user);
        }

        IPage<WXApproval> page = new Page<>(po.getPage(), po.getLimit());
        QueryWrapper<WXApproval> wrapper = new QueryWrapper<>();
        if (ObjectUtil.isNotNull(po.getStartTime())) {
            wrapper.gt(ObjectUtil.isNotNull(po.getStartTime()), "apply_time", DateUtil.beginOfDay(po.getStartTime()));
        }
        if (ObjectUtil.isNotNull(po.getEndTime())){
            wrapper.lt(ObjectUtil.isNotNull(po.getEndTime()), "apply_time", DateUtil.endOfDay(po.getEndTime()));
        }
        if (ObjectUtil.isNotNull(po.getPaymentTime())) {
            wrapper.eq("payment_time", po.getPaymentTime());
        }
        wrapper.eq(StrUtil.isNotBlank(po.getSpStatus()), "sp_status", po.getSpStatus());
        wrapper.eq(StrUtil.isNotBlank(po.getPaymentStatus()), "payment_status", po.getPaymentStatus());
        wrapper.eq(StrUtil.isNotBlank(po.getReimbursementType()), "reimbursement_type", po.getReimbursementType());
        wrapper.eq(StrUtil.isNotBlank(po.getUserId()), "user_id", po.getUserId());
        wrapper.eq(ObjectUtil.isNotNull(po.getRegionId()), "region_id", po.getRegionId());
        // 添加数据权限过滤：userIds由DataPermissionAspect注入
        if (CollectionUtil.isNotEmpty(po.getUserIds())) {
            wrapper.in("user_id", po.getUserIds());
        }
        wrapper.orderByDesc("apply_time");
        IPage<WXApproval> approvalList = baseMapper.selectPage(page, wrapper);

        wrapper.select("sum(money) totalMoney");
        wrapper.in("sp_status", Arrays.asList("PASSED", "ALREADY_PAY"));
        WXApproval totalMoney = baseMapper.selectOne(wrapper);


        result.put("approvalList", approvalList);
        result.put("userList", userList);
        result.put("totalMoney", ObjectUtil.isNull(totalMoney) ? 0 :  totalMoney.getTotalMoney());
        return result;
    }

    /**
     * 获取access_token
     * 注意：SDK已经自动管理access_token的获取、缓存和刷新，无需手动调用此方法
     * 保留此方法仅用于特殊场景，建议使用wxCpService.getXxxService()的方法，SDK会自动处理token
     * @return
     * @throws Exception
     */
    @Deprecated
    private String getAccessToken() throws Exception {
        try {
            // 使用SDK获取access_token，SDK会自动处理token的缓存和刷新
            return wxCpService.getAccessToken();
        } catch (WxErrorException e) {
            log.error("获取access_token失败", e);
            throw new Exception("获取access_token失败: " + e.getMessage());
        }
    }

    /**
     * 获取审批单号列表
     * 使用SDK的getApprovalInfo方法获取最近5天的审批单号
     */
    private List<String> getReleaseApprovalList() throws Exception {
        try {
            Date now = new Date();
            Date startTime = DateUtil.offsetDay(now, -5);
            
            // 使用SDK获取审批信息，SDK会自动处理access_token
            WxCpApprovalInfo approvalData = wxCpService.getOaService().getApprovalInfo(startTime, now, 0, 100, null);
            log.info("拉取审批集合结果：{}", JSONObject.toJSONString(approvalData));
            
            List<String> ids = approvalData.getSpNoList();
            return ids != null ? ids : new ArrayList<>();
        } catch (WxErrorException e) {
            log.error("获取审批单号列表失败", e);
            throw new Exception("获取审批单号列表失败: " + e.getMessage());
        }
    }

    /**
     * 获取审批单详情
     * 使用SDK的getApprovalDetail方法获取指定审批单的详细信息
     */
    public WxCpApprovalDetailResult getReleaseApprovalDetail(String spNo) throws WxErrorException {
        // 使用SDK获取审批详情，SDK会自动处理access_token
        return wxCpService.getOaService().getApprovalDetail(spNo);
    }

    /**
     * 解析报销类型（已废弃）
     * 此方法用于从JSON解析报销类型，现在应使用SDK的ApplyDataContent对象直接获取
     */
    @Deprecated
    private String resolveReimbursementType(JSONObject contentJson) {
        JSONObject info = contentJson.getJSONObject("info");
        JSONObject applyData = info.getJSONObject("apply_data");
        JSONArray contents = applyData.getJSONArray("contents");
        for(int j = 0; j< contents.size(); j++){
            JSONObject item = contents.getJSONObject(j);
            if("Selector".equals(item.get("control").toString())){
                Object value = item.get("value");
                JSONObject valueJson = JSONObject.parseObject(JSONObject.toJSONString(value));
                JSONObject selector = valueJson.getJSONObject("selector");
                JSONArray options = selector.getJSONArray("options");
                JSONObject jsonObject = options.getJSONObject(0);
                JSONArray array = jsonObject.getJSONArray("value");
                for(int i = 0; i < array.size(); i++){
                    JSONObject now = array.getJSONObject(i);
                    if("zh_CN".equals(now.getString("lang"))){
                        log.info("报销费用：{}", now.get("text"));
                        return now.getString("text");
                    }
                }
            }
        }
        return "";
    }

    private WXApproval selectBySPNo(String spNo){
        QueryWrapper<WXApproval> wrapper = new QueryWrapper<>();
        wrapper.eq("sp_no", spNo);
        return this.baseMapper.selectOne(wrapper);
    }

    @Override
    public boolean updatePaymentStatus(UpdatePaymentStatusPO po) {
        // 验证审批编号列表
        if (CollectionUtil.isEmpty(po.getSpNoList())) {
            log.warn("审批编号列表为空，无法更新");
            return false;
        }
        
        log.info("开始批量更新付款状态，审批编号数量: {}", po.getSpNoList().size());
        
        // 批量查询审批记录
        List<WXApproval> approvalList = selectBySPNOList(po.getSpNoList());
        if (CollectionUtil.isEmpty(approvalList)) {
            log.warn("未找到任何审批记录，审批编号列表: {}", po.getSpNoList());
            return false;
        }
        
        // 批量更新
        int successCount = 0;
        for (WXApproval approval : approvalList) {
            try {
                // 更新打款账户和打款时间
                WXApproval updateEntity = new WXApproval();
                updateEntity.setId(approval.getId());
                updateEntity.setPaymentAccount(po.getPaymentAccount());
                updateEntity.setPaymentTime(po.getPaymentTime());
                
                // 如果打款时间不为空，同时更新打款状态为已支付
                if (po.getPaymentTime() != null) {
                    updateEntity.setPaymentStatus("10"); // 10表示已支付
                    updateEntity.setSpStatus("ALREADY_PAY"); // 同时更新审批状态为已支付
                    
                    // 异步同步状态到企业微信（不影响主流程）
                    asyncWechatService.syncApprovalStatusToWechat(approval, "ALREADY_PAY");
                }
                
                boolean updated = this.updateById(updateEntity);
                if (updated) {
                    successCount++;
                    log.info("更新付款状态成功，审批编号: {}", approval.getSpNo());
                } else {
                    log.warn("更新付款状态失败，审批编号: {}", approval.getSpNo());
                }
            } catch (Exception e) {
                log.error("更新付款状态时发生异常，审批编号: {}", approval.getSpNo(), e);
            }
        }
        
        log.info("批量更新付款状态完成，总数: {}, 成功: {}", approvalList.size(), successCount);
        return successCount > 0;
    }
    
    @Override
    @Deprecated
    public boolean syncApprovalStatusToWechat(String spNo, String status) {
        log.warn("syncApprovalStatusToWechat(String, String)方法已废弃，请使用AsyncWechatService.syncApprovalStatusToWechat(WXApproval, String)");
        
        // 查询审批记录
        WXApproval approval = selectBySPNO(spNo);
        if (approval == null) {
            log.warn("未找到审批编号为 {} 的审批记录", spNo);
            return false;
        }
        
        // 调用异步方法
        asyncWechatService.syncApprovalStatusToWechat(approval, status);
        return true;
    }
}
